<?php
/**
 * Created by PhpStorm.
 * User: ytlmi
 * Date: 2018/3/12
 * Time: 10:37
 */

namespace org\util\forensictool\forensicreport;

use org\util\forensictool\ForensicCalculate;
use org\util\forensictool\LittleTools;
use org\util\wordtool\Word;

class Report3l extends ReportQz
{
    /**
     * @throws \Exception
     */
    protected function makeDetectionTable()
    {
        $tempPage = Word::instance()->createTemp();
        $roleGroup = $this->makeRoleGroup();

        //设置单元格宽度
        $positionMap = ['first' => self::FIRST_ROW_STYLE, 'mid' => self::MID_ROW_STYLE, 'last' => self::LAST_ROW_STYLE];
        $width = [1500, 1500, 1500, 2000, 1500, 1500];

        //每个亲代与每个子代生成对比表格
        $tableIndex = 0;
        foreach ($roleGroup[1] as $child) {
            $tableIndex++;
            $calResult = ForensicCalculate::instance()
                ->setCaseType($this->caseData['case_type'])
                ->setGenotypeF($this->caseData['samples']['F']['genotype'])
                ->setGenotypeM($this->caseData['samples']['M']['genotype'])
                ->setGenotypeC($this->caseData['samples'][$child]['genotype'])
                ->setFrequency($this->frequency)
                ->setMutation($this->mutation)
                ->calculate();//计算
            $childSampleName = $this->caseData['samples'][$child]['sample_name'];//样品名
            $fatherSampleName = $this->caseData['samples']['F']['sample_name'];//样品名
            $motherSampleName = $this->caseData['samples']['M']['sample_name'];//样品名
            $arrMarker = array_keys($calResult);//全部基因座
            $tableDes = '表' . $tableIndex . '：' . $childSampleName . '和' . $fatherSampleName . '、' . $motherSampleName . '号检材STR基因座的基因分型结果';//表头
            $tableHead = ['基因座', $motherSampleName, $childSampleName, $fatherSampleName, '亲权指数'];//第一行
//            $tableHead = ['基因座', $motherSampleName, $childSampleName, $fatherSampleName, '亲权指数', '公式'];//第一行
            $tempPage->addPr($tableDes, self::TABLE_DES_FONT, self::TEXT_TAB+['spaceAfter'=>30,'spaceBefore'=>30]);
            $table = $tempPage->addTable(self::TABLE_STYLE);
            $table->addSimpleRow($tableHead, $width, self::TABLE_FONT, $positionMap['first']);
            foreach ($calResult as $marker => $result) {
                $pi = isset($result[0]) ? sprintf("%.2f", $result[0]) : '-';//无计算结果时用“-”代替
                $alleleC = $this->caseData['samples'][$child]['genotype'][$marker];//孩子在当前基因座的基因型
                $alleleF = $this->caseData['samples']['F']['genotype'][$marker];//亲代基因型
                $alleleM = $this->caseData['samples']['M']['genotype'][$marker];//亲代基因型
                $content = [$marker, $alleleM[0] . (isset($alleleM[1]) ? ',' . $alleleM[1] : ''), $alleleC[0] . (isset($alleleC[1]) ? ',' . $alleleC[1] : ''), $alleleF[0] . (isset($alleleF[1]) ? ',' . $alleleF[1] : ''), $pi];
                //                $content = [$marker, $alleleM[0] . ',' . $alleleM[1], $alleleC[0] . ',' . $alleleC[1], $alleleF[0] . ',' . $alleleF[1], $pi, $result[1] ?? ''];
                $position = $marker == end($arrMarker) ? 'last' : 'mid';
                $table->addSimpleRow($content, $width, self::TABLE_FONT, $positionMap[$position]);
            }
        }
        return $tempPage;
    }

    /**
     * @throws \Exception
     */
    public function makeRecord()
    {
        $rep = parent::makeRecord();

        $tempPage = Word::instance()->createTemp();
        $roleGroup = $this->makeRoleGroup();

        //设置单元格宽度
        $positionMap = ['first' => self::FIRST_ROW_STYLE, 'mid' => self::MID_ROW_STYLE, 'last' => self::LAST_ROW_STYLE];
        $width = [1500, 1500, 1500, 2000, 1500];

        //每个亲代与每个子代生成对比表格
        $tableIndex = 0;
        foreach ($roleGroup[1] as $child) {
            $tableIndex++;
            $calResult = ForensicCalculate::instance()
                ->setCaseType($this->caseData['case_type'])
                ->setGenotypeF($this->caseData['samples']['F']['genotype'])
                ->setGenotypeM($this->caseData['samples']['M']['genotype'])
                ->setGenotypeC($this->caseData['samples'][$child]['genotype'])
                ->setFrequency($this->frequency)
                ->setMutation($this->mutation)
                ->calculate();//计算
            $childSampleName = $this->caseData['samples'][$child]['sample_name'];//样品名
            $fatherSampleName = $this->caseData['samples']['F']['sample_name'];//样品名
            $motherSampleName = $this->caseData['samples']['M']['sample_name'];//样品名
            $arrMarker = array_keys($calResult);//全部基因座
            $tableHead = ['基因座', $motherSampleName, $childSampleName, $fatherSampleName,'公式', '亲权指数'];//第一行
            $table = $tempPage->addTable(self::TABLE_STYLE);
            $table->addSimpleRow($tableHead, $width, self::TABLE_FONT, $positionMap['first']);
            foreach ($calResult as $marker => $result) {
                $pi = isset($result[0]) ? sprintf("%.2f", $result[0]) : '-';//无计算结果时用“-”代替
                $alleleC = $this->caseData['samples'][$child]['genotype'][$marker];//孩子在当前基因座的基因型
                $alleleF = $this->caseData['samples']['F']['genotype'][$marker];//亲代基因型
                $alleleM = $this->caseData['samples']['M']['genotype'][$marker];//亲代基因型
                $position = $marker == end($arrMarker) ? 'last' : 'mid';
                $row = $table->addRow();
                $row->addCell(self::TABLE_FONT, $positionMap[$position])->addPr($marker,self::TABLE_FONT,$positionMap[$position]);
                $row->addCell(self::TABLE_FONT, $positionMap[$position])->addPr($alleleC[0] . ',' . $alleleC[1],self::TABLE_FONT,$positionMap[$position]);
                $row->addCell(self::TABLE_FONT, $positionMap[$position])->addPr($alleleF[0] . ',' . $alleleF[1],self::TABLE_FONT,$positionMap[$position]);
                $row->addCell(self::TABLE_FONT, $positionMap[$position])->addPr($alleleM[0] . ',' . $alleleM[1],self::TABLE_FONT,$positionMap[$position]);
                $tcFormula = $row->addCell(self::TABLE_FONT, $positionMap[$position]);
                $tcFormula->addPr('',self::TABLE_FONT,$positionMap[$position]);
                if (isset($result[1])) {
                    $formulaPart = preg_split('/[{}^]/', $result[1]);
                    foreach ($formulaPart as $index => $val) {
                        if ($index % 2 == 0) {
                            $font=self::TABLE_FONT;
                        } else {
                            $font=self::TABLE_FONT+['sub'=>true];
                        }
                        $tcFormula->addText($val,$font);
                    }
                } else {
                    $tcFormula->addText('-',self::TABLE_FONT);
                }
                $row->addCell(self::TABLE_FONT, $positionMap[$position])->addPr($pi,self::TABLE_FONT,$positionMap[$position]);
            }
        }
        $rep['CAL_TABLE']=$tempPage;
        $reportTemplate = $_SERVER['DOCUMENT_ROOT'].'/template/forensic/record.docx';
        $reportSavePath = $_SERVER['DOCUMENT_ROOT'].'/report/forensic/'.$this->caseData['case_id']. iconv('UTF-8','GB2312//IGNORE','-检验记录表.docx') ;
        Word::instance()->setTemplate($rep,$reportTemplate,$reportSavePath);
    }

    /**
     * @throws \Exception
     */
    //生成DNA部分分析说明
    protected function makeDescribe()
    {
        $describeDom = Word::instance()->createTemp();//分析部分
        $concludeDom = Word::instance()->createTemp();//结论部分
        $roleGroup = $this->makeRoleGroup();//角色表
        $arr_marker = array_keys($this->caseData['samples'][$roleGroup[0][0]]['genotype']);//TODO
        $markerNum = count($arr_marker);//基因座数量
        $strNum = $markerNum - 1;
        $describeDom->addPr($arr_marker[0] . '等' . $strNum . '个STR基因座均为人类的遗传学标记，遵循孟德尔遗传定律，联合应用可进行亲权鉴定，其CPE大于0.9999。', self::BODY_FONT, self::TEXT_TAB);
        $concludeDom->addText('依据现有资料和DNA检验结果,', self::BODY_FONT, self::TEXT_TAB);
        $conclude = '';
        foreach ($roleGroup[1] as $child) {//每个孩子
            $childName = $this->caseData['samples'][$child]['person_name'];//姓名
            $fatherName = $this->caseData['samples']['F']['person_name'];//姓名

            $calResult = ForensicCalculate::instance()
                ->setCaseType($this->caseData['case_type'])
                ->setGenotypeF($this->caseData['samples']['F']['genotype'])
                ->setGenotypeM($this->caseData['samples']['M']['genotype'])
                ->setGenotypeC($this->caseData['samples'][$child]['genotype'])
                ->setFrequency($this->frequency)
                ->setMutation($this->mutation)
                ->calculate();//计算并获取结果

            $strFailMarker = null;
            $failMarker = [];
            $failCount = 0;
            $CPI_data = 1;

            foreach ($calResult as $marker => $result) {
                if (isset($result[2]) && $result[2] == '不匹配') {//不匹配项汇总
                    $failMarker[] = $marker;
                    $strFailMarker .= $marker . '、';
                    $failCount++;
                }
                if (isset($result[0])) {//计算CPI
                    $CPI_data *= $result[0];
                }
            }

            $arr_CPI = LittleTools::ciFang($CPI_data);
            $strFailMarker = mb_substr($strFailMarker, 0, -1);

            if ($CPI_data < 1) {//否定结论
                $describe = '在' . $arr_marker[0] . '等' . $strNum . '个STR基因座，'
                    . $childName . '在' . $strFailMarker . '等' . $failCount
                    . '个基因座的等位基因无法从' . $fatherName . '的基因型中找到来源，按照'
                    . $this->config['standard_qz'] . '中亲权指数的计算方法，累积亲权指数为' . $arr_CPI[0];
                $conclude .= '不支持' . $fatherName . '为' . $childName . '的生物学父亲；';

            } elseif ($CPI_data > 10000) {
                if ($failCount > 0) {//有突变
                    $describeP0 = '在' . $arr_marker[0] . '等' . $strNum . '个STR基因座，'
                        . '除' . $strFailMarker . '基因座外，'
                        . $fatherName . '均能提供给孩子必需的等位基因';
                    $describeP1 = '';
                    foreach ($failMarker as $failed) {
                        $alleleC[0] = $this->caseData['samples'][$child]['genotype'][$failed][0];
                        $alleleC[1] = $this->caseData['samples'][$child]['genotype'][$failed][1];
                        $alleleP[0] = $this->caseData['samples']['F']['genotype'][$failed][0];
                        $alleleP[1] = $this->caseData['samples']['F']['genotype'][$failed][1];
                        $describeP1 .= '在' . $failed . '基因座，'
                            . $childName . '的基因型为“' . $alleleC[0] . ',' . $alleleC[1] . '”，'
                            . $fatherName . '的基因型为“' . $alleleP[0] . ',' . $alleleP[1] . '”，'
                            . $fatherName . '不能提供给孩子必需的等位基因' . $alleleC[0] . '或' . $alleleC[1]
                            . '，不符合遗传规律。按照' . $this->config['standard_qz'] . '中不符合遗传规律情形时亲权指数的计算方法，'
                            . $failed . '基因座的亲权指数为' . sprintf("%.2f", $calResult[$failed][0]) . '；';
                    }
                    $describeP1 = mb_substr($describeP1, 0, -1);
                    $describeDom->addPr('');
                    $describeP2 = '。综上' . $strNum . '个STR 基因座的累积亲权指数为' . $arr_CPI[0];
                    $describe = $describeP0 . $describeP1 . $describeP2;

                } else {//肯定结论
                    $describe = '在' . $arr_marker[0] . '等' . $strNum . '个STR基因座，'
                        . $childName . '的等位基因均可从' . $fatherName . '的基因型中找到来源，按照'
                        . $this->config['standard_qz'] . '中亲权指数的计算方法，累积亲权指数为' . $arr_CPI[0];
                }
                $conclude .= '支持' . $fatherName . '为' . $childName . '的生物学父亲；';

            }else{
                $describe = '需补充检测';
                $conclude .= '需补充检测';
            }
            $describeDom->addPr($describe, self::BODY_FONT, self::TEXT_TAB)
                ->addText($CPI_data < 10000 ? '' : '×10',self::BODY_FONT)
                ->addText($CPI_data < 10000 ? '' : $arr_CPI[1],self::BODY_FONT+['super'=>true])
                ->addText('。', self::BODY_FONT);
        }

        $conclude = mb_substr($conclude, 0, -1);
        $conclude .= '。';
        $concludeDom->addText($conclude, self::BODY_FONT, self::TEXT_TAB);
        $this->describe = $describeDom;
        $this->conclude = $concludeDom;
    }
}